package com.wpp;

import org.junit.Test;

import java.io.FileInputStream;
import java.io.InputStream;
import java.util.Properties;

/*
 * 1.反射机制与面向对象中的封装性是不是矛盾的？如何看待两个技术？
 * 答：不矛盾。封装性是建议我们怎么调私有方法等，而反射是关于能不能调的问题
 * 2.反射的特征：动态性
 * 3.关于java.lang.Class的理解
 *      3.1.类的加载过程：
 *      程序经过javac.exe命令以后。会生成一个或者多个字节码文件(.class结尾)，
 *      接着我们使用java.exe命令对某个字节码文件进行解释运行，相当于将某个字节码文件加载到内存中，此过程
 *      就称为类的加载。加载到内存中的类，就称为运行时类，此运行时类，就作为Class的一个实例。
 *      3.2.换句话说，Class的实例就对应着一个运行时类
 *      3.3.加载到内存中的运行时类，会缓存一定的时间，在此时间之内，我们可以通过不同的方式来获取此运行时类
 *
 *
 *
 * */
public class ReflectionTest {

    @Test
    public void test() throws ClassNotFoundException {
        //获取大Class的实例的四种方式
        //方式一:调用运行时类的属性：.class
        Class<Person> cls1 = Person.class;
        System.out.println(cls1);

        //方式二：通过运行类的对象
        Person person = new Person();
        Class cls2 = person.getClass();
        System.out.println(cls2);

        //方式三：类的全类名，调用Class的静态方法：forName(String classPath)
        Class cls3 = Class.forName("com.wpp.Person");
        System.out.println(cls3);

        //方式四：使用类的加载器：Classloder
        ClassLoader classLoader = ReflectionTest.class.getClassLoader();
        Class cls4 = classLoader.loadClass("com.wpp.Person");
        System.out.println(cls4);
    }

    /*
     * 读取配置文件的两种方式
     * 1.读取配置文件的方式一：
     * 2.读取配置文件的方式二：使用Classloader
     *
     * */


    @Test
    public void test1() throws Exception {

        Properties properties = new Properties();
        //读取配置文件方式一：文件默认是在 module下的
//        FileInputStream fis = new FileInputStream("jdbc.properties");
//        properties.load(fis);

        //方式二：使用Classloader，文件默认是在src文件下的
        ClassLoader classLoader = ReflectionTest.class.getClassLoader();
        InputStream is = classLoader.getResourceAsStream("jdbc.properties");
        properties.load(is);


        String user = properties.getProperty("user");
        String password = properties.getProperty("password");
        System.out.println("user:" + user + ".密码是：" + password);
    }

}
